package com.sc.nft.controller;

import com.sc.nft.annotation.SysMemberLogin;
import com.sc.nft.annotation.UserLogin;
import com.sc.nft.controller.request.IdPageRequest;
import com.sc.nft.controller.request.IdRequest;
import com.sc.nft.controller.request.NameRequest;
import com.sc.nft.entity.UserInfo;
import com.sc.nft.entity.dto.*;
import com.sc.nft.entity.dto.*;
import com.sc.nft.entity.vo.*;
import com.sc.nft.enums.RedisKeyEnum;
import com.sc.nft.exception.GlobalRunTimeException;
import com.sc.nft.pool.UserPool;
import com.sc.nft.service.CopyrightAuctionRecordService;
import com.sc.nft.service.CopyrightAuctionRoundService;
import com.sc.nft.service.CopyrightAuctionService;
import com.sc.nft.sup.PageRequest;
import com.sc.nft.sup.PageResult;
import com.sc.nft.sup.Result;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.redisson.Redisson;
import org.redisson.api.RLock;
import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.validation.Valid;
import java.util.List;
import java.util.concurrent.TimeUnit;


@Slf4j
@RequiredArgsConstructor
@RestController
@RequestMapping("/copyrightAuction")
@Api(tags = "版权商品竞拍模块")
public class CopyrightAuctionController {


    private final CopyrightAuctionService copyrightAuctionService;

    private final CopyrightAuctionRecordService copyrightAuctionRecordService;

    private final CopyrightAuctionRoundService copyrightAuctionRoundService;
    private final Redisson redisson;


    @ApiOperation(value = "报名竞拍活动获取信息", notes = "报名竞拍活动获取信息", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/registration/details", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public Result<CopyrightAuctionRegistrationDetailsVO> registrationDetails(@RequestBody IdRequest idRequest) {
        return Result.success(copyrightAuctionService.registrationDetails(UserPool.getUser(),idRequest.getId()));
    }


    @ApiOperation(value = "报名活动或修改起拍价", notes = "报名活动或修改起拍价", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/registration", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public Result registration(@RequestBody CopyrightAuctionRegistrationDTO registrationDTO) {
        UserInfo user = UserPool.getUser();
        if (!registrationDTO.getPaymentPassword().equals(UserPool.getUser().getTransactionPassword())) {
            throw new GlobalRunTimeException("支付密码错误");
        }
        copyrightAuctionService.registration(user,registrationDTO);
        return Result.success();
    }


    @ApiOperation(value = "市场版权拍卖商品", notes = "市场版权商品", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/market", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public PageResult<CopyrightMarketAuctionDTO> market(@RequestBody PageRequest pageRequest) {
        return PageResult.success(copyrightAuctionService.market(pageRequest.getPageNo(),pageRequest.getPageSize()));
    }


    @ApiOperation(value = "市场版权拍卖商品详情", notes = "市场版权拍卖商品详情", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/market/details", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public Result<CopyrightMarketAuctionDetailsVO> marketDetails(@Valid @RequestBody IdRequest idRequest) {
        return Result.success(copyrightAuctionService.marketDetails(idRequest.getId(),UserPool.getUser()));
    }


    @ApiOperation(value = "市场版权拍卖用户出价", notes = "市场版权拍卖用户出价", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/market/bid", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public Result marketBid(@Valid @RequestBody CopyrightMarketAuctionBidDTO auctionBidDTO) {
        if (!auctionBidDTO.getPaymentPassword().equals(UserPool.getUser().getTransactionPassword())) {
            throw new GlobalRunTimeException("支付密码错误");
        }
        RLock lock = redisson.getLock(RedisKeyEnum.SECOND_BID_PRODUCTS_LOCK.getKey() + auctionBidDTO.getId());
        RLock userLock = redisson.getLock(RedisKeyEnum.USER_SCROLL_SHOP_ORDER.getKey() + UserPool.getUser().getId());
        try {
            boolean res = lock.tryLock(3, TimeUnit.SECONDS);
            if (res) {

                boolean userLockRes = userLock.tryLock(3, TimeUnit.SECONDS);
                if(!userLockRes){
                    return Result.fail("请稍后重试!");
                }
                copyrightAuctionService.marketBid(auctionBidDTO,UserPool.getUser());
            }else{
                return Result.fail("请稍后重试!");
            }
        } catch (InterruptedException e) {
            e.printStackTrace();
            throw new GlobalRunTimeException("系统超时");
        } finally {
            lock.unlock();
            userLock.unlock();
        }

        return Result.success();
    }

    @ApiOperation(value = "结果公示", notes = "结果公示", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/market/winList", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public Result<List<CopyrightAuctionWinListVO>> auctionWinList(@Valid @RequestBody IdRequest idRequest) {
        return Result.success(copyrightAuctionService.auctionWinList(idRequest.getId()));
    }

    @ApiOperation(value = "当前用户拍卖记录", notes = "当前用户拍卖记录", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/record/userList", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public PageResult<CopyrightAuctionRecordUserListVO> auctionWinList(@Valid @RequestBody CopyrightAuctionRecordUserDTO copyrightAuctionRecordUserDTO) {
        copyrightAuctionRecordUserDTO.setUserId(UserPool.getUser().getId());
        return PageResult.success(copyrightAuctionRecordService.copyrightAuctionRecordUserList(copyrightAuctionRecordUserDTO.getUserId(),copyrightAuctionRecordUserDTO.toMp()));
    }


    @ApiOperation(value = "当前用户参与记录 轮次", notes = "当前用户参与记录 轮次", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/round/userList", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public Result<List<CopyrightAuctionRoundUserListVO>> copyrightAuctionRoundUserList(@Valid @RequestBody IdRequest idRequest) {
        return Result.success(copyrightAuctionRoundService.copyrightAuctionRoundUserList(idRequest.getId(),UserPool.getUser().getId()));
    }

    @ApiOperation(value = "市场版权拍卖商品搜索", notes = "市场版权拍卖商品搜索", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/market/search", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public PageResult<CopyrightMarketAuctionDTO> marketSearch(@RequestBody CopyrightAuctionNameDTO copyrightAuctionNameDTO) {
        return PageResult.success(copyrightAuctionService.marketSearch(copyrightAuctionNameDTO.getName(),copyrightAuctionNameDTO.getPageNo(),copyrightAuctionNameDTO.getPageSize()));
    }

    @ApiOperation(value = "市场版权拍卖开启时间", notes = "市场版权拍卖开启时间", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/market/openTime", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public Result<CopyrightAuctionOpenTimeVO> marketOpenTime() {
        return PageResult.success(copyrightAuctionService.marketOpenTime());
    }

    @ApiOperation(value = "获取用户协议", notes = "获取用户协议", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/getRule", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public Result<String> auctionGetRule() {
        return Result.success(copyrightAuctionService.auctionGetRule());
    }

    @ApiOperation(value = "用户是否同意协议", notes = "获取用户协议", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/userAgreement", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public Result<Boolean> userAgreement() {
        return Result.success(copyrightAuctionService.userAgreement(UserPool.getUser().getId()));
    }


    @ApiOperation(value = "同意用户协议", notes = "获取用户协议", httpMethod = "POST", produces = MediaType.APPLICATION_JSON_VALUE)
    @PostMapping(value = "/user/agreement", produces = MediaType.APPLICATION_JSON_VALUE)
    @UserLogin
    public Result auctionUserAgreement() {
        copyrightAuctionService.auctionUserAgreement(UserPool.getUser().getId());
        return Result.success();
    }



}
